home *** CD-ROM | disk | FTP | other *** search
/ Language/OS - Multiplatform Resource Library / LANGUAGE OS.iso / lisp / kcl / akcl / akcl1615.lha / mp / mp_divul3.c < prev    next >
C/C++ Source or Header  |  1991-03-19  |  1KB  |  45 lines

  1. /*
  2.     ulong low,divisor,h,q;
  3.     if divisor!= 0 and if (hiremainder:low)/divisor (ie q)
  4.         is expressible in 32 bits,
  5.     then
  6.     (h = hiremainder, q = divll(low,divisor),
  7.       h:low == q * divisor + hiremainder && 0<= hiremainder && hiremainder < divisor)
  8.     is TRUE.  
  9.     [the arithmetic is ordinary arithmetic among unsigned 64 bit integers]
  10.     A sufficient criteria for (hiremainder:low)/divisor
  11.          to be expressible in 32 bits,
  12.     is bfffo(divisor)-bfffo(hiremainder) <= 0
  13.     
  14. */   
  15.  
  16. #include "include.h"
  17. #include "arith.h"
  18.  
  19. #define WORD_SIZE 32
  20. /* SHIFT1BIT: shift h and l left by 1 as 64 bits.  We don't care what
  21.   is coming into the bottom word  */
  22.  
  23. #define shift1bit(h,l) \
  24.   l = (h = h << 1, ( l & (1<<(WORD_SIZE -1)) ? h +=1 : 0), l<<1)
  25.  
  26. divul3(x,y,hi)
  27.      ulong x,y,*hi;
  28. {ulong q =0;
  29.  ulong h = *hi,l=x,hibit;
  30.  int count = WORD_SIZE;
  31. /* if (y<=h) printf("error: the quotient will be more than 32 bits"); */
  32. #ifdef QUICK_DIV
  33.  QUICK_DIV(x,y,h,hi)
  34. #endif 
  35.   do { q = q << 1;
  36.      hibit = h & (1 << (WORD_SIZE -1));
  37.      shift1bit(h,l);
  38.      if (hibit || (y <= h))
  39.        { q += 1; h -= y;}
  40.      } while(--count > 0);
  41.  *hi = h;
  42.  return q;
  43. }
  44.  
  45.